﻿using System;
using System.IO;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Data.Sql;
using System.Data.SqlClient;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Xml;
using AvvaMobileNHibernateHelperKit.DAO;
using AvvaMobileNHibernateHelperKit.Utils;

using RD.Metadata.Database.Sql;

using log4net;
using log4net.Config;

namespace AvvaMobileNHibernateHelperKit
{
    public partial class MainForm : Form
    {
        #region log4net
        protected static readonly ILog log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);
        #endregion
    	
        static MainForm()
        {
            try
            {
                XmlConfigurator.Configure(new FileInfo(@"C:\cygwin\home\rseward\src\nhhk\AvvaMobileNHibernateHelperKit1\log4net.xml")); ;
            }
            catch (Exception ignored) { }
            log.Debug("log4net has been initialized");
        }
    	
        // TODO: hack to check the write tables        
        Project project = Project.CurrentProject;
        // Project project = new MedsProject();

        [STAThread]
        static void Main()
        {
            Application.Run(new MainForm());
        }

        public Project Project {
        	get {
        		// refresh the data model from the values specified on the form
        		if (!cmbServerNames.InvokeRequired) {
        			RefreshProject();
        		}
        		return project;        		        	
        	}
        }
        
        /// <summary>
        /// Refresh the data model from the UI.
        /// </summary>
        public void RefreshProject()
        {
        	project.ServerName = cmbServerNames.Text;
        	project.InstanceName = txtInstanceName2.Text;
        	project.DatabaseName = cmbDatabaseNames.Text;
        	project.Password = txtPassword.Text;
        	project.Username = txtUsername.Text;
        	
        	List<string> selectedTables = new List<string>();        	
			for (int i = 0; i <= chklistTables.Items.Count - 1; i++)
        	{
				if (chklistTables.GetItemCheckState(i) == CheckState.Checked) {
					selectedTables.Add( chklistTables.Items[i].ToString() );					
				}
			}
			project.SelectedTables = selectedTables.ToArray();			
			project.ProjectDir = txtProjectFolder.Text;
			project.AssemblyName = txtAssemblyName.Text;
			project.Namespace = txtDefaultNamespace.Text; 
			project.CopyLog4netDll = chkCopyLog4netDll.Checked;
			project.CopyNHibernateDll = chkCopyNhibernateDll.Checked;
			project.CopyNullablesDll = chkCopyNullablesDll.Checked;
			project.DynamicUpdate = chkDynamicUpdate.Checked;
			
			LanguageGenerator classGenerator = LanguageGenerator.CSharp;
			if (rdoVBNET.Checked) {
				classGenerator = LanguageGenerator.VBNet;
			}
			
			project.ClassLanguageGenerator = classGenerator;
			
        }

        public void PopulateForm(Project model)
        {
            cmbDatabaseNames.Text = project.DatabaseName;
            txtInstanceName2.Text = project.InstanceName;
            txtDefaultNamespace.Text = project.Namespace;
            txtAssemblyName.Text = project.AssemblyName;
            txtPassword.Text = project.Password;
            txtProjectFolder.Text = project.ProjectDir;
            txtProjectFile.Text = project.ProjectFile;
            cmbServerNames.Text = project.ServerName;
            txtUsername.Text = project.Username;
            chkCopyNhibernateDll.Checked = project.CopyNHibernateDll;
            chkCopyLog4netDll.Checked = project.CopyLog4netDll;
            chkCopyNullablesDll.Checked = project.CopyNullablesDll;
            chkDynamicUpdate.Checked = project.DynamicUpdate;

            chklistTables.Items.Clear();
            foreach (string table in project.SelectedTables)
            {
                chklistTables.Items.Add(table, true);
            }
            
            rdoCSharp.Checked = false;
            rdoVBNET.Checked = false;
            
            if (project.ClassLanguageGenerator == LanguageGenerator.VBNet) {
            	rdoVBNET.Checked = true;
            } else {
            	rdoCSharp.Checked = true;
            }
        }
    	
        public MainForm()
        {
            InitializeComponent();
        }

        Framework.Data dataClass = new Framework.Data();

        private void SetConnectionString()
        {
        	Project proj = this.Project;
        	String instanceName = "";
        	if (!String.IsNullOrEmpty( proj.InstanceName ) ) {
        		instanceName = @"\" + proj.InstanceName;
        	}
        	
            dataClass.ConnectionString = "server=" + proj.ServerName + instanceName + ";database=" + proj.DatabaseName + ";user id=" + proj.Username + ";password=" + proj.Password + ";";
            System.Console.WriteLine( dataClass.ConnectionString );
        }

        private void btnRefreshServerNames_Click(object sender, EventArgs e)
        {
            try
            {
                this.Cursor = Cursors.WaitCursor;
                cmbServerNames.DataSource = System.Data.Sql.SqlDataSourceEnumerator.Instance.GetDataSources();
                cmbServerNames.DisplayMember = "ServerName";
            }
            catch(Exception ex)
            {
                MessageBox.Show(ex.Message, "Server Names", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
            finally
            {
                this.Cursor = Cursors.Default;
            }
        }

        private void rdoSqlAuthentication_CheckedChanged(object sender, EventArgs e)
        {
            pnlUserInfo.Enabled = (rdoSqlAuthentication.Checked) ? true : false;
        }

        private void comboBox1_DropDown(object sender, EventArgs e)
        {
            try
            {
                this.Cursor = Cursors.WaitCursor;
                dataClass.ConnectionString = "server=" + cmbServerNames.Text + ";database=master;user id=" + txtUsername.Text + ";password=" + txtPassword.Text + ";";
                cmbDatabaseNames.DataSource = dataClass.GetDatabaseNames("select name, dbid from sysdatabases");
                cmbDatabaseNames.DisplayMember = "name";
                cmbDatabaseNames.ValueMember = "dbid";
            }
            finally
            {
                this.Cursor = Cursors.Default;
            }
        }

        private void MainForm_Load(object sender, EventArgs e)
        {
            PopulateForm(project);
        }

        private void btnTestConnection_Click(object sender, EventArgs e)
        {
            try
            {
                this.Cursor = Cursors.WaitCursor;
                SetConnectionString();
                dataClass.TestConnection();
                MessageBox.Show("Test connection succeeded", "Connection", MessageBoxButtons.OK, MessageBoxIcon.Information);
            }
            catch(Exception ex)
            {
                MessageBox.Show("Connection for "+ dataClass.ConnectionString + "failed with this exception: "+ ex.Message, "Connection", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
            finally
            {
                this.Cursor = Cursors.Default;
            }
        }

        private void loadViews()
        {
            SetConnectionString();
            DataTable dt = dataClass.ExecuteReader("SELECT [ViewName] = so.name, [ID] = so.id FROM sysobjects so WHERE OBJECTPROPERTY(so.id, 'IsMsShipped') = 0 AND so.xtype = 'V' ORDER BY so.name");

            foreach (DataRow dr in dt.Rows)
            {
                chklistTables.Items.Add(dr["ViewName"]);
            }
        }

        private void loadTables()
        {
                SetConnectionString();
                DataTable dt = dataClass.ExecuteReader("SELECT [TableName] = so.name, [ID] = so.id FROM sysobjects so WHERE OBJECTPROPERTY(so.id, 'IsMsShipped') = 0 AND so.xtype = 'U' ORDER BY so.name");
                chklistTables.Items.Clear();
                foreach(DataRow dr in dt.Rows)
                {
                    chklistTables.Items.Add(dr["TableName"]);
                }
                loadViews();

                foreach(string selectedTable in project.SelectedTables) {
                	int idx = chklistTables.Items.IndexOf(selectedTable);
                	
                	if ( idx > -1 ) {
                		chklistTables.SetItemChecked(idx, true);
                	}
                }        	
        }

        private void btnNext_Click(object sender, EventArgs e)
        {
            tabMain.SelectedIndex = 1;
            try
            {
                this.Cursor = Cursors.WaitCursor;
                loadTables();                
            }
            catch(Exception ex)
            {
                MessageBox.Show(ex.Message, "Load Tables", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
            finally
            {
                this.Cursor = Cursors.Default;
            }
        }
        
        private void btnLoadTables_Click(object sender, EventArgs e)
        {
            try
            {
                this.Cursor = Cursors.WaitCursor;
                loadTables();                
            }
            catch(Exception ex)
            {
                MessageBox.Show(ex.Message, "Load Tables", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
            finally
            {
                this.Cursor = Cursors.Default;
            }
        }

        private void button1_Click(object sender, EventArgs e)
        {
            try
            {
                this.Cursor = Cursors.WaitCursor;
                SetConnectionString();
                DataTable dt = dataClass.GetTableColumnsInfo("EXEC dbo.sp_MShelpcolumns '" + chklistTables.SelectedItem.ToString() + "'");
                ColumnsPreview previewForm = new ColumnsPreview(dt);
                previewForm.ShowDialog();
                
            }
            catch(Exception ex)
            {
                MessageBox.Show(ex.Message, "Columns Preview", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
            finally
            {
                this.Cursor = Cursors.Default;
            }
        }

        private void button1_Click_1(object sender, EventArgs e)
        {
            tabMain.SelectedIndex = 2;
        }

        private void linkLabel2_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e)
        {
            System.Diagnostics.Process.Start("mailto:myilmaz@dotnetishere.com");
        }

        private void linkLabel1_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e)
        {
            System.Diagnostics.Process.Start("http://www.dotnetishere.com");
        }

        private void linkLabel3_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e)
        {
            System.Diagnostics.Process.Start("mailto:myilmaz@avvamobile.com");
        }

        private void linkLabel4_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e)
        {
            System.Diagnostics.Process.Start("http://www.avvamobile.com");
        }

        private void pictureBox1_Click(object sender, EventArgs e)
        {
            System.Diagnostics.Process.Start("http://www.avvamobile.com");
        }

        private void pictureBox2_Click(object sender, EventArgs e)
        {
            System.Diagnostics.Process.Start("http://www.dotnetishere.com");
        }       

        private void button3_Click(object sender, EventArgs e)
        {
            Generate();
        }

        private void button2_Click_1(object sender, EventArgs e)
        {
            tabMain.SelectedIndex = 3;
        }

        /*
        private string getPropertyName( string tableName, string colName)
        {
        	string propName = colName;
        	if (tableName.Equals(colName)) {
        		propName += "_";
        	}
        	
        	return propName;
        }*/
        
        
        private void Generate()
        {
            string status = "without";
            try
            {
            	// assume the project model is already refreshed
                SetCursor(  Cursors.WaitCursor );
                Progress("Generating starting", 0);
                System.Threading.Thread.Sleep(2000);
                Progress("Generating started", 0);

                #region Check bin Directory Exist And Create
                    
                if(!System.IO.Directory.Exists(txtProjectFolder.Text + @"\bin"))
                {
                    System.IO.Directory.CreateDirectory(txtProjectFolder.Text + @"\bin");
                }

                if(!System.IO.Directory.Exists(txtProjectFolder.Text + @"\App_Code"))
                {
                    System.IO.Directory.CreateDirectory(txtProjectFolder.Text + @"\App_Code");
                }

                if(!System.IO.Directory.Exists(txtProjectFolder.Text + @"\App_Code\NHMappings"))
                {
                    System.IO.Directory.CreateDirectory(txtProjectFolder.Text + @"\App_Code\NHMappings");
                }

                #endregion

                #region Copy Files(Assemblies)
                Progress("Assemblies copying", 5);
                string projectPath = @"c:\program files\Avva Mobile Enterprise Solutions\NHibernate Helper Kit";

                if(chkCopyNhibernateDll.Checked){
                    System.IO.File.Copy(projectPath + @"\NHibernate.dll", txtProjectFolder.Text + @"\bin\NHibernate.dll", true);
                    Progress("NHibernate assembly copied", 0);
                }

                if(chkCopyLog4netDll.Checked){
                    System.IO.File.Copy(projectPath + @"\log4net.dll", txtProjectFolder.Text + @"\bin\log4net.dll", true);
                    Progress("Log4net assembly copied", 0);
                }

                if(chkCopyNullablesDll.Checked){
                    System.IO.File.Copy(projectPath + @"\Nullables.dll", txtProjectFolder.Text + @"\bin\Nullables.dll", true);
                    Progress("Nullables assembly copied", 0);
                }
                Progress("Selected assemblies copied", 10);
                #endregion

                #region Write NHibernate Config File
                
                Progress("NHibernate config file writing", 15);
                System.IO.StreamWriter sw = new System.IO.StreamWriter(txtProjectFolder.Text + @"\bin\hibernate.cfg.xml");
                sw.WriteLine("<?xml version=\"1.0\" encoding=\"utf-8\"?>");
                sw.WriteLine("<hibernate-configuration xmlns=\"urn:nhibernate-configuration-2.0\">");
                sw.WriteLine("<session-factory>");
                sw.WriteLine("<property name=\"connection.provider\">NHibernate.Connection.DriverConnectionProvider</property>");
                sw.WriteLine("<property name=\"connection.driver_class\">NHibernate.Driver.SqlClientDriver</property>");
                sw.WriteLine("<property name=\"connection.connection_string\">Server=" + project.ServerName + ";initial catalog=" + project.DatabaseName + ";User Id=" + project.Username + ";Password=" + project.Password + ";</property>");
                sw.WriteLine("<property name=\"show_sql\">true</property>");
                sw.WriteLine("<property name=\"dialect\">NHibernate.Dialect.MsSql2000Dialect</property>");
                sw.WriteLine("<property name=\"use_outer_join\">true</property>");
                sw.WriteLine("<mapping assembly=\"" + txtAssemblyName.Text + "\" />");
                sw.WriteLine("</session-factory>");
                sw.WriteLine("</hibernate-configuration>");               
                sw.Flush();
                sw.Close();
                sw.Dispose();

                Progress("NHibernate config file generated", 20);

                #endregion

                Progress("Setting connection", 25);
                // SetConnectionString();
                Progress("Connection set", 30);

                if(rdoCSharp.Checked)
                {
                    CSharp_MsSql();
                }
                else if (rdoVBNET.Checked)
                {
                    VBNet_MsSql();
                }

                #region Write XML(*.hbm.xml)Config Files

                NewWriteHbmXmlFiles();
                
                #endregion                

                MessageBox.Show("Generating process completed " + status + " errors.", "Generate Files", MessageBoxButtons.OK, MessageBoxIcon.Information);
            } /*
            catch (Exception ex)
            {
                Progress(ex.Message, 0);
                MessageBox.Show(ex.Message, "Generate Files", MessageBoxButtons.OK, MessageBoxIcon.Error);
                status = "with";
                log.Debug("Exception generating files: ", ex);
            } */
            finally
            {
                Progress("Generating process completed " + status + " errors.", 100);                
                SetCursor( Cursors.Default );
            }
        }

        delegate void SetCursorCallback(Cursor cursor);

        private void SetCursor(Cursor cursor)
        {
            if (this.InvokeRequired)             
            {
                SetCursorCallback call = new SetCursorCallback(SetCursor);
                this.Invoke(call, new object[] { cursor });
            } else {
                this.Cursor = cursor;
            }
        }
        
        private void NewWriteHbmXmlFiles()
        {
        	HbmXmlFileGenerator hbmXmlGen = new HbmXmlFileGenerator(this, this.dataClass, this.Project);
        	
        	hbmXmlGen.DynamicUpdate = chkDynamicUpdate.Checked;
        	
        	hbmXmlGen.GenerateFiles();
        }
        
        private void WriteHbmXmlFiles()
        {
        	Progress("Config files writing", 70);
        	log.Debug("Config files writing");

        	for (int i = 0; i <= chklistTables.Items.Count - 1; i++)
        	{
        		if (chklistTables.GetItemCheckState(i) == CheckState.Checked)
        		{
        			string tableName = chklistTables.Items[i].ToString();
        			string className = tableName ;
        			System.IO.StreamWriter sw3 = new System.IO.StreamWriter(txtProjectFolder.Text + @"\App_Code\NHMappings\" + className + ".hbm.xml");
        			DataTable dt = dataClass.GetTableColumnsInfo("EXEC dbo.sp_MShelpcolumns '" + tableName + "'");

        			SqlMetaTable tabMeta = dataClass.GetTableInfo(tableName);
        			
        			if (tabMeta!=null) {
        				log.Debug("Meta info about tableName="+tableName+" has the following meta columns");
        				foreach (SqlMetaColumn col in tabMeta.Columns) {
        					log.Debug("Tab Meta Data: "+col.ColumnName+" "+col.DbType+" PK="+col.IsPrimaryKey);
        				}
        			} else {
        				log.Debug("Meta data for tableName="+tableName+" was not loaded");
        			}
        			
        			
        			//                        foreach (DataRow col in colData.Rows) {
//
        			//                        }
        			
        			sw3.WriteLine("<?xml version=\"1.0\" encoding=\"utf-8\" ?>");
        			sw3.WriteLine("<hibernate-mapping xmlns=\"urn:nhibernate-mapping-2.2\">");

        			string dynamicUpdate = "";
        			if (chkDynamicUpdate.Checked) { dynamicUpdate = "dynamic-update=\"true\""; }
        			sw3.WriteLine("<class name=\"" + txtDefaultNamespace.Text + "." + className + ", " + txtAssemblyName.Text + "\" table=\"" + tableName + "\" " + dynamicUpdate + ">");

        			log.Debug("table_name="+tableName);
        			bool lb_firstCol = true;
        			foreach (DataRow dr in dt.Rows)
        			{
        				string colName = dr["col_name"].ToString();
        				string propName = NameUtils.GetPropertyName( className, colName);

        				// TODO: be more flexible in defining the primary key of the table. E.g. support GUIDs.
        				if (lb_firstCol) {
        					log.Debug("col_name="+dr["col_name"]+"col_identity="+dr["col_identity"]);
        					
        					
        				}
        				
        				if (Convert.ToInt32(dr["col_identity"]) == 1)
        				{
        					sw3.WriteLine("<id name=\"" + colName + "\" column=\"" + colName + "\" type=\"Int32\" unsaved-value=\"0\">");
        					sw3.WriteLine("<generator class=\"identity\" />");
        					sw3.WriteLine("</id>");
        				}
        				else
        				{
        					switch (dr["col_typename"].ToString())
        					{
        						case "int":
        							sw3.WriteLine("<property name=\"" + propName + "\" column=\"" + colName + "\" type=\"Int32\" length=\"" + dr["col_len"].ToString() + "\" />"); break;
        						case "tinyint":
        							sw3.WriteLine("<property name=\"" + propName + "\" column=\"" + colName + "\" type=\"Int32\" length=\"" + dr["col_len"].ToString() + "\" />"); break;
        						case "smallint":
        							sw3.WriteLine("<property name=\"" + propName + "\" column=\"" + colName + "\" type=\"Int32\" length=\"" + dr["col_len"].ToString() + "\" />"); break;
        						case "bigint":
        							sw3.WriteLine("<property name=\"" + propName + "\" column=\"" + colName + "\" type=\"Int32\" length=\"" + dr["col_len"].ToString() + "\" />"); break;
        						case "char":
        							sw3.WriteLine("<property name=\"" + propName + "\" column=\"" + colName + "\" type=\"String\" length=\"" + dr["col_len"].ToString() + "\" />"); break;
        						case "varchar":
        							sw3.WriteLine("<property name=\"" + propName + "\" column=\"" + colName + "\" type=\"String\" length=\"" + dr["col_len"].ToString() + "\" />"); break;
        						case "nchar":
        							sw3.WriteLine("<property name=\"" + propName + "\" column=\"" + colName + "\" type=\"String\" length=\"" + dr["col_len"].ToString() + "\" />"); break;
        						case "nvarchar":
        							sw3.WriteLine("<property name=\"" + propName + "\" column=\"" + colName + "\" type=\"String\" length=\"" + dr["col_len"].ToString() + "\" />"); break;
        						case "datetime":
        							sw3.WriteLine("<property name=\"" + propName + "\" column=\"" + colName + "\" type=\"DateTime\" />"); break;
        						case "smalldatetime":
        							sw3.WriteLine("<property name=\"" + propName + "\" column=\"" + colName + "\" type=\"DateTime\" />"); break;
        						case "money":
        							sw3.WriteLine("<property name=\"" + propName + "\" column=\"" + colName + "\" type=\"Decimal\" />"); break;
        						case "decimal":
        							sw3.WriteLine("<property name=\"" + propName + "\" column=\"" + colName + "\" type=\"Decimal\" />"); break;
        						case "smallmoney":
        							sw3.WriteLine("<property name=\"" + propName + "\" column=\"" + colName + "\" type=\"Decimal\" />"); break;
        						case "bit":
        							sw3.WriteLine("<property name=\"" + propName + "\" column=\"" + colName + "\" type=\"Boolean\" />"); break;
        						case "uniqueidentifier":
        							sw3.WriteLine("<property name=\"" + propName + "\" column=\"" + colName + "\" type=\"Guid\" length=\"30\" />"); break;
        						case "text":
        							sw3.WriteLine("<property name=\"" + propName + "\" column=\"" + colName + "\" type=\"String\" />"); break;
        						case "ntext":
        							sw3.WriteLine("<property name=\"" + propName + "\" column=\"" + colName + "\" type=\"String\" />"); break;
        					}
        				}
        			}

        			sw3.WriteLine("</class>");
        			sw3.WriteLine("");
        			sw3.WriteLine("</hibernate-mapping>");
        			sw3.Flush();
        			sw3.Close();
        			sw3.Dispose();
        		}
        	}

        	Progress("Config files generated", 100);
        }

        private void toolStripButton1_Click(object sender, EventArgs e)
        {
        	RefreshProject();
        	SetConnectionString();
            System.Threading.Thread t = new System.Threading.Thread((new System.Threading.ThreadStart(Generate)));
            t.Start();
        }

        delegate void ProgressCallback(string progress, int value);
   
        public void Progress(string progress, int value)
        {
            if (ProgressBar.InvokeRequired)
            {
                ProgressCallback call = new ProgressCallback(Progress);
                this.Invoke(call, new object[] { progress, value });
            }
            else
            {
                log.Debug(progress);

                lblStatus.Text = progress + "...";
                if (value > 100)
                {
                    ProgressBar.Value = 100; toolStripProgressBar1.Value = 100;
                }
                else if (value == 0)
                { }
                else
                {
                    ProgressBar.Value = value; toolStripProgressBar1.Value = value;
                }
                lboxProcesses.Items.Add(progress + "...");
                lboxProcesses.SelectedIndex = lboxProcesses.Items.Count - 1;
            }

            System.Threading.Thread.Sleep(20);
        }


        private void toolStripLabel1_Click_1(object sender, EventArgs e)
        {
            new AboutBox().ShowDialog();
        }

        private void toolStripButton2_Click(object sender, EventArgs e)
        {
            new AboutBox().ShowDialog();
        }

        private void btnCheckAll_Click(object sender, EventArgs e)
        {
            for (int i = 0; i <= chklistTables.Items.Count - 1; i++)
            {
                chklistTables.SetItemChecked(i, true);
            }
        }

        private void btnUnCheckAll_Click(object sender, EventArgs e)
        {
             for (int i = 0; i <= chklistTables.Items.Count - 1; i++)
            {
                chklistTables.SetItemChecked(i, false);
            }
        }

        private void btnBrowseProjectFolder_Click(object sender, EventArgs e)
        {
            FolderBrowserDialog fbd = new FolderBrowserDialog();
            fbd.SelectedPath = txtProjectFolder.Text;
      
            if (fbd.ShowDialog().Equals(DialogResult.OK) && (!fbd.SelectedPath.Equals(null)))
            {
                txtProjectFolder.Text = fbd.SelectedPath;
            }
        }

        #region Generators

        private void VBNet_MsSql()
        {
        	VbNetClassGenerator gen = new VbNetClassGenerator(this, this.dataClass, this.Project);
        	
        	gen.GenerateClasses();
        }


        private void CSharp_MsSql()
        {
        	CSharpClassGenerator gen = new CSharpClassGenerator(this, this.dataClass, this.Project);
        	
        	gen.GenerateClasses();
        }

        #endregion

        private static Dictionary<string, string> env = new Dictionary<string, string>();

        private void btnProjectBrowse_Click_1(object sender, EventArgs e)
        {
            if (!env.ContainsKey("ProjectXmlDir"))
            {
                env["ProjectXmlDir"] = @"C:\cygwin\home\rseward\nhhk\";
            }
            string projectXmlDir = env["ProjectXmlDir"];

            openFileDialog1.InitialDirectory = projectXmlDir;
            openFileDialog1.ShowDialog();
            openFileDialog1.DefaultExt = "xml";
            openFileDialog1.CheckFileExists = true;

            if (!String.IsNullOrEmpty(openFileDialog1.FileName))
            {
                FileInfo projFile = new FileInfo(openFileDialog1.FileName);

                if (projFile.Exists)
                {
                    Project proj = ProjectDao.Instance.GetProject(projFile.FullName);

                    if (proj != null)
                    {
                        this.project = proj;
                        PopulateForm(project);
                    }
                    else
                    {
                        MessageBoxUtils.ShowMessage(this, "Unable to load project: "+projFile.FullName, "Unable to load project", MessageBoxIcon.Error);
                    }
                }
            }
        }

        private void btnSaveProject_Click(object sender, EventArgs e)
        {
            RefreshProject();

            FileInfo projFile = new FileInfo(project.ProjectFile);

            if (!projFile.Directory.Exists)
            {
                projFile.Directory.Create();
            }


            ProjectDao.Instance.SaveProject(project);

            MessageBoxUtils.ShowMessage(this, "Project saved to " + projFile.FullName, "Project Saved", MessageBoxIcon.Error);
        }

    }
}
